package com.zys.http.ui.tab.panel;

import com.intellij.openapi.actionSystem.ActionManager;
import com.intellij.openapi.actionSystem.ActionToolbar;
import com.intellij.openapi.actionSystem.DefaultActionGroup;
import com.intellij.openapi.fileTypes.FileType;
import com.intellij.openapi.project.Project;
import com.intellij.openapi.ui.ComboBox;
import com.intellij.ui.JBColor;
import com.intellij.ui.components.JBPanel;
import com.intellij.util.ui.JBUI;
import com.zys.http.action.CommonAction;
import com.zys.http.constant.HttpEnum;
import com.zys.http.entity.ReqHistory;
import com.zys.http.entity.param.ParamProperty;
import com.zys.http.extension.service.Bundle;
import com.zys.http.tool.HttpClient;
import com.zys.http.tool.UrlTool;
import com.zys.http.tool.ui.ComboBoxTool;
import com.zys.http.ui.dialog.EditorDialog;
import com.zys.http.ui.editor.CustomEditor;
import com.zys.http.ui.icon.HttpIcons;
import jdk.jfr.Description;
import lombok.Getter;
import org.jetbrains.annotations.NotNull;

import javax.swing.*;
import java.awt.*;
import java.util.Map;

/**
 * @author zys
 * @since 2025-02-19
 */
@Getter
public class RequestBodyPanel extends JBPanel<RequestBodyPanel> implements TabOperation {
    private final CustomEditor bodyEditor;
    @Description("请求体类型")
    private final ComboBox<FileType> bodyFileType;

    public RequestBodyPanel(Project project) {
        super(new BorderLayout(0, 0));
        this.setBorder(JBUI.Borders.customLine(JBColor.PanelBackground, 0, 3, 0, 0));
        this.bodyEditor = new CustomEditor(project);
        this.bodyEditor.setName("BODY");
        this.add(this.bodyEditor, BorderLayout.CENTER);

        JLabel label = new JLabel(Bundle.get("http.api.tab.body.type.label"));
        this.bodyFileType = ComboBoxTool.fileTypeComboBox(itemListener(bodyEditor));

        JPanel bodySelectPanel = new JPanel(new BorderLayout(0, 0));
        bodySelectPanel.add(label, BorderLayout.WEST);
        bodySelectPanel.add(bodyFileType, BorderLayout.CENTER);
        DefaultActionGroup group = createActionGroup(project);

        ActionToolbar component = (ActionToolbar) ActionManager.getInstance()
                .createActionToolbar("http.body.editor", group, true).getComponent();
        component.setReservePlaceAutoPopupIcon(false);
        component.setTargetComponent(bodyEditor);
        bodySelectPanel.add((JComponent) component, BorderLayout.EAST);
        this.add(bodySelectPanel, BorderLayout.SOUTH);
    }

    private @NotNull DefaultActionGroup createActionGroup(Project project) {
        DefaultActionGroup group = new DefaultActionGroup();
        CommonAction action = new CommonAction(Bundle.get("http.api.tab.body.action.edit"), "", HttpIcons.General.FULL_SCREEN);
        action.setAction(e -> {
            EditorDialog dialog = new EditorDialog(project, Bundle.get("http.api.tab.body.action.edit.dialog"), bodyEditor.getFileType(), bodyEditor.getText());
            dialog.setOkCallBack(bodyEditor::setText);
            dialog.show();
        });
        group.add(action);
        return group;
    }

    @Override
    public void reset() {
        this.bodyEditor.setText("");
    }

    @Override
    public void execute(HttpEnum.HttpMethod httpMethod, HttpEnum.ContentType contentType, String param, Map<String, ParamProperty> paramPropertyMap) {
        ParamProperty v = paramPropertyMap.get(param);
        HttpEnum.ParamUsage usage = v.getParamUsage();
        switch (usage) {
            case URL -> {
                if (httpMethod.equals(HttpEnum.HttpMethod.POST)) {
                    // 将参数格式化成 username=a&password=a
                    String s = UrlTool.buildParamPropertyUrlParameters(paramPropertyMap, false);
                    this.bodyEditor.setText(s, ComboBoxTool.TEXT_FILE_TYPE);
                    this.bodyFileType.setSelectedItem(ComboBoxTool.TEXT_FILE_TYPE);
                }
            }
            case BODY -> {
                if (contentType.equals(HttpEnum.ContentType.APPLICATION_JSON)) {
                    this.bodyEditor.setText(v.getDefaultValue().toString(), ComboBoxTool.JSON_FILE_TYPE);
                    this.bodyFileType.setSelectedItem(ComboBoxTool.JSON_FILE_TYPE);
                } else {
                    this.bodyEditor.setText(v.getDefaultValue().toString(), ComboBoxTool.TEXT_FILE_TYPE);
                    this.bodyFileType.setSelectedItem(ComboBoxTool.TEXT_FILE_TYPE);
                }
            }
            default -> {
            }
        }
    }

    @Override
    public void recover(ReqHistory history) {
        this.bodyEditor.setText(history.getBody(), HttpClient.parseFileType(history.getContentType()));
        this.bodyFileType.setSelectedItem(HttpClient.parseFileType(history.getContentType()));
    }
}
